跳到主要内容

Go 的缓冲 IO 包 bufio

bufio 库它主要是在io库上加了一层缓存的功能,

注意缓存 Cache 和缓冲 Buffer 的区别

  • buffer(缓冲)是为了提高内存和硬盘(或其他I/0设备)之间的数据交换的速度而设计的。
  • cache(缓存)是为了提高 cpu 和内存之间的数据交换速度而设计,也就是平常见到的一级缓存、二级缓存、三级缓存(也叫内存缓存)。

读取文件

以下是 bufio 读取文件的例子:

package main

import (
"bufio"
"fmt"
"os"
"strconv"
)

func main() {
fileObj, err := os.Open("config.yml")
if err != nil {
fmt.Println("文件打开失败:", err)
return
}

defer fileObj.Close()
// 使用 bufio.NewReader 去初始化一个 Reader 对象,
// 存在 buffer 中的数据,读取一次就会被清空
reader := bufio.NewReader(fileObj)
buf := make([]byte, 1024)
//读取 Reader 对象中的内容到 []byte 类型的 buf 中
info, err := reader.Read(buf)
if err != nil {
fmt.Println(err)
}

fmt.Println("读取的字节数:" + strconv.Itoa(info))
fmt.Printf("读取的文件内容: \n %s \n", string(buf))
}

读取单行

如果不想自己使用 buffer 去拿数据,也可以使用提供的 ReadString 读取一行

func readBigFile(filePath string) error {
f, err := os.Open(filePath)
defer f.Close()

if err != nil {
log.Fatal(err)
return err
}

buf := bufio.NewReader(f)
count := 0
for {
count += 1
line, err := buf.ReadString('\n')
line = strings.TrimSpace(line)
if err != nil {
return err
}
fmt.Println("line", line)
// 这里是避免全部打印
if count > 100 {
break
}
}
return nil
}

写操作

package main
import (
"bufio"
"fmt"
"os"
)


func main() {
name := "demo.txt"
content := "hello world!"

fileObj, err := os.OpenFile(name, os.O_RDWR|os.O_CREATE|os.O_APPEND, 0644)

if err != nil {
fmt.Println("文件打开失败", err)
}

defer fileObj.Close()

writeObj := bufio.NewWriterSize(fileObj, 4096)
//使用 Write 方法,需要使用 Writer 对象的 Flush 方法将 buffer 中的数据刷到磁盘

buf := []byte(content)
if _, err := writeObj.Write(buf); err == nil {
if err := writeObj.Flush(); err != nil {
panic(err)
}
fmt.Println("数据写入成功")
}
}

与 ioutil 结合使用 ⭐

import (
"bufio"
"fmt"
"io/ioutil"
"os"
)

func main() {
fileObj, err := os.Open("config.yml")
if err != nil {
fmt.Println("文件打开失败:", err)
return
}

defer fileObj.Close()
reader := bufio.NewReader(fileObj)
buf, err := ioutil.ReadAll(reader)

if err != nil {
fmt.Println(err)
}

fmt.Printf("读取的文件内容: \n %s \n", string(buf))
}